package com.buli.blmall.admin.utils;

import com.alibaba.fastjson2.JSON;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import org.apache.http.util.EntityUtils;

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.util.Map;

/**
 * @author xiang.gao
 * @date 2024/12/18 13:33
 */
public class HttpUtil {

    //最大连接数
    private static final int MAX_TOTAL_CONNECTIONS = 50;
    //每个路由的最大并发连接数 于同一个目标服务器（即同一个路由），你可以同时打开的最大HTTP连接数
    private static final int DEFAULT_MAX_PER_ROUTE = 10;
    //连接超时
    private static final int CONNECT_TIMEOUT = 3000;
    //返回超时
    private static final int SOCKET_TIMEOUT = 3000;

    private static CloseableHttpClient httpClient;

    static {
        //连接池配置
        PoolingHttpClientConnectionManager connectionManager = new PoolingHttpClientConnectionManager();
        connectionManager.setMaxTotal(MAX_TOTAL_CONNECTIONS);
        connectionManager.setDefaultMaxPerRoute(DEFAULT_MAX_PER_ROUTE);
        //请求配置
        RequestConfig requestConfig = RequestConfig.custom()
                .setConnectTimeout(CONNECT_TIMEOUT)
                .setSocketTimeout(SOCKET_TIMEOUT)
                .build();
        //Http客户端
        httpClient = HttpClients.custom()
                .setConnectionManager(connectionManager)
                .setDefaultRequestConfig(requestConfig)
                .build();
    }

    /**
     * get无参请求
     * @param url
     * @return
     * @throws IOException
     */
    public static String doGet(String url) throws IOException {
        return doGet(url, String.class);
    }

    /**
     * get无参请求
     * @param url
     * @param tClass
     * @return
     * @param <T>
     * @throws IOException
     */
    public static <T> T doGet(String url, Class<T> tClass) throws IOException {
        HttpGet httpGet = new HttpGet(url);
        try (CloseableHttpResponse response = httpClient.execute(httpGet)) {
            HttpEntity entity = response.getEntity();
            if (entity != null) {
                return parseResponse(entity, tClass);
            }
        }
        return null;
    }

    /**
     * post 请求
     * @param url
     * @param parameter
     * @param tClass
     * @return
     * @param <T>
     * @throws IOException
     */
    public static <T> T doJsonPost(String url, Map<String, Object> parameter, Class<T> tClass) throws IOException {
        HttpPost httpPost = new HttpPost(url);
        httpPost.setHeader("Content-Type", "application/json");
        httpPost.setEntity(new StringEntity(JSON.toJSONString(parameter), StandardCharsets.UTF_8));

        try (CloseableHttpResponse response = httpClient.execute(httpPost)) {
            HttpEntity entity = response.getEntity();
            if (entity != null) {
                return parseResponse(entity, tClass);
            }
        }
        return null;
    }

    /**
     * post 请求
     * @param url
     * @param jsonPayload
     * @param tClass
     * @return
     * @param <T>
     * @throws IOException
     */
    public static <T> T doJsonPost(String url, String jsonPayload, Class<T> tClass) throws IOException {
        HttpPost httpPost = new HttpPost(url);
        httpPost.setHeader("Content-Type", "application/json");
        httpPost.setEntity(new StringEntity(jsonPayload, StandardCharsets.UTF_8));

        try (CloseableHttpResponse response = httpClient.execute(httpPost)) {
            HttpEntity entity = response.getEntity();
            if (entity != null) {
                return parseResponse(entity, tClass);
            }
        }
        return null;
    }

    /**
     * 解析响应内容
     * @param entity
     * @param tClass
     * @param <T>
     * @return
     * @throws IOException
     */
    private static <T> T parseResponse(HttpEntity entity, Class<T> tClass) throws IOException {
        Header contentType = entity.getContentType();
        String responseBody = EntityUtils.toString(entity, StandardCharsets.UTF_8);

        if (contentType != null && contentType.getValue().toLowerCase().contains("application/json")) {
            return JSON.parseObject(responseBody, tClass);
        } else {
            // 如果不是 JSON 格式，返回原始字符串
            return (T) responseBody;
        }
    }



}
